package com.iespring.service.admin;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.iespring.bean.admin.user.bo.ConfigBo;
import com.iespring.bean.admin.user.bo.ConfigExpressBo;
import com.iespring.bean.admin.user.entity.*;
import com.iespring.bean.admin.user.vo.*;
import com.iespring.bean.common.Admin;
import com.iespring.bean.common.BasePageInfo;
import com.iespring.bean.common.BaseRespVo;
import com.iespring.bean.common.CommonData;
import com.iespring.mapper.admin.*;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.subject.Subject;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;

import javax.annotation.Resource;
import java.io.Serializable;
import java.lang.reflect.Field;
import java.util.*;

/**
 * @author xD
 * @since 2022/12/28 19:33
 */
@Service
public class AdminAuthServiceImpl implements AdminAuthService {


    @Resource
    private AdminAuthMapper adminAuthMapper;

    @Resource
    private MallGoodsMapper mallGoodsMapper;

    @Resource
    private MallGoodsProductMapper mallGoodsProductMapper;

    @Resource
    private MallUserMapper mallUserMapper;

    @Resource
    private MallOrderMapper mallOrderMapper;

    @Resource
    private MallAddressMapper mallAddressMapper;

    @Resource
    private MallCollectMapper mallCollectMapper;

    @Resource
    private MallFootprintMapper mallFootprintMapper;

    @Resource
    private MallSearchHistoryMapper mallSearchHistoryMapper;

    @Resource
    private MallFeedbackMapper mallFeedbackMapper;

    @Resource
    private MallSystemMapper mallSystemMapper;

    @Override
    public LoginUserVo login(UsernamePasswordToken token) {
        //拿到subject对象
        //如果认证成功会返回true
        Subject subject = SecurityUtils.getSubject();
        subject.login(token);
        boolean authenticated = subject.isAuthenticated();
        if (authenticated) {
            //获取认证成功后的用户信息
            MallAdmin userInfo = (MallAdmin) subject.getPrincipals().getPrimaryPrincipal();
            //获取sessionId
            Serializable sessionId = subject.getSession().getId();
            AdminInfo adminInfo = new AdminInfo();
            adminInfo.setAvatar(userInfo.getAvatar());
            adminInfo.setNickName(userInfo.getUsername());
            LoginUserVo loginUserVo = new LoginUserVo();
            loginUserVo.setAdminInfo(adminInfo);
            loginUserVo.setToken((String) sessionId);
            return loginUserVo;
        }
        return null;
    }

    @Override
    public AuthInfoVo info() {
        //查询用户的角色信息role_ids
        List<Admin> admins = adminAuthMapper.selectRoleIds();
        AuthInfoVo resp = new AuthInfoVo();
        Subject subject = SecurityUtils.getSubject();
//        MallAdmin admin = (MallAdmin) subject.getPrincipals().getPrimaryPrincipal();
//        Admin admin = admins.get(0);
        MallAdmin admin = null;
        PrincipalCollection principals = subject.getPrincipals();
        if (principals != null) {
            admin = (MallAdmin) principals.getPrimaryPrincipal();
        }
        Integer[] roleIds = admin.getRoleIds();
        List<Integer> roleList = Arrays.asList(roleIds);
        resp.setAvatar(admin.getAvatar());
        resp.setName(admin.getUsername());
        //根据roleids去对应role表中查询 name：超级管理员、商场管理员..
        List<String> names = adminAuthMapper.selectRoleNamesByRoleIds(roleList);
        resp.setRoles(names);
        //根据roleids去对应perms表中查询 permission
//        List<String> perms = adminAuthMapper.selectPermsByRoleIds(roleList);
        List<String> perms = adminAuthMapper.selectPermsByRoleIds2(roleList);
        //TODO 逻辑完善
        if (ObjectUtils.isEmpty(perms) || names.contains("超级管理员")) {
            //若没有结果,则为超级管理员
            perms.add("*");
            resp.setPerms(perms);
        }else {
            resp.setPerms(perms);
        }
        return resp;
    }

    /**
     * 首页
     *
     * @since 2022/12/29 15:54
     */
    @Override
    public DashBoardVo dashboard() {
        Integer goodsCount = mallGoodsMapper.selectCount();
        Integer orderCount = mallOrderMapper.selectCount();
        Integer goodsProductCount = mallGoodsProductMapper.selectCount();
        Integer userCount = mallUserMapper.selectCount();
        return new DashBoardVo(goodsCount, userCount, goodsProductCount, orderCount);
    }

    /**
     * 会员页
     *
     * @since 2022/12/29 15:54
     */
    @Override
    public CommonData userList(BasePageInfo pageInfo) {
        //开启分页功能
        PageHelper.startPage(pageInfo.getPage(), pageInfo.getLimit());
        List<MallUser> mallUsers = mallUserMapper.selectAllUserLimit(pageInfo);
        PageInfo<MallUser> userPageInfo = new PageInfo<>(mallUsers);
        return CommonData.data(userPageInfo);
    }

    /**
     * 修改用户信息
     *
     * @since 2022/12/29 15:54
     */
    @Override
    public BaseRespVo userUpdate(MallUser mallUser) {
        int result = mallUserMapper.updateByPrimaryKeySelective(mallUser);
        return BaseRespVo.ok(result);
    }

    /**
     * 收货地址
     *
     * @since 2022/12/29 15:53
     */
    @Override
    public CommonData addressList(BasePageInfo basePageInfo) {
        //开启分页功能
        PageHelper.startPage(basePageInfo.getPage(), basePageInfo.getLimit());
        List<MallAddress> addresses = mallAddressMapper.selectAllAddressLimit(basePageInfo);
        PageInfo<MallAddress> mallAddressPageInfo = new PageInfo<>(addresses);
        return CommonData.data(mallAddressPageInfo);
    }

    /**
     * 根据id查询user
     *
     * @since 2022/12/29 15:58
     */
    @Override
    public MallUser userDetail(Integer id) {
        return mallUserMapper.selectByPrimaryKey(id);
    }

    /**
     * 会员收藏页
     *
     * @since 2022/12/29 16:05
     */
    @Override
    public CommonData collectList(BasePageInfo basePageInfo) {
        //开启分页功能
        PageHelper.startPage(basePageInfo.getPage(), basePageInfo.getLimit());
        List<MallCollect> mallCollects = mallCollectMapper.selectAllCollectLimit(basePageInfo);
        PageInfo<MallCollect> mallCollectPageInfo = new PageInfo<>(mallCollects);
        return CommonData.data(mallCollectPageInfo);
    }

    /**
     * 会员足迹
     *
     * @since 2022/12/29 16:44
     */
    @Override
    public CommonData footprintList(BasePageInfo basePageInfo) {
        //开启分页功能
        PageHelper.startPage(basePageInfo.getPage(), basePageInfo.getLimit());
        List<MallFootprint> mallFootprints = mallFootprintMapper.selectFootprintLimit(basePageInfo);
        PageInfo<MallFootprint> mallFootprintPageInfo = new PageInfo<>(mallFootprints);
        return CommonData.data(mallFootprintPageInfo);
    }

    /**
     * 搜索历史
     *
     * @since 2022/12/29 17:04
     */
    @Override
    public CommonData historyList(BasePageInfo basePageInfo) {
        //开启分页功能
        PageHelper.startPage(basePageInfo.getPage(), basePageInfo.getLimit());
        List<MallSearchHistory> mallSearchHistories = mallSearchHistoryMapper.selectAllHistoryLimit(basePageInfo);
        PageInfo<MallSearchHistory> mallSearchHistoryPageInfo = new PageInfo<>(mallSearchHistories);
        return CommonData.data(mallSearchHistoryPageInfo);
    }

    /**
     * 意见反馈
     *
     * @since 2022/12/29 17:21
     */
    @Override
    public CommonData feedbackList(BasePageInfo basePageInfo) {
        //开启分页功能
        PageHelper.startPage(basePageInfo.getPage(), basePageInfo.getLimit());
        List<MallFeedback> mallFeedbacks = mallFeedbackMapper.selectAllFeedback(basePageInfo);
        PageInfo<MallFeedback> mallFeedbackPageInfo = new PageInfo<>(mallFeedbacks);
        return CommonData.data(mallFeedbackPageInfo);
    }

    /**
     * 用户统计
     *
     * @since 2022/12/29 19:44
     */
    @Override
    public StatUserVo statUser() {
        List<RowsBean> rows = mallUserMapper.selectUserOrderByDay();
        Field[] fields = RowsBean.class.getDeclaredFields();
        ArrayList<String> list = new ArrayList<>();
        for (Field field : fields) {
            list.add(field.getName());
        }
        return new StatUserVo(list, rows);
    }

    @Override
    public StatUserVo statOrder() {
        List<RowsOrderBean> rowsOrderBeans = mallOrderMapper.selectOrderStatistics();
        Field[] fields = RowsOrderBean.class.getDeclaredFields();
        ArrayList<String> list = new ArrayList<>();
        for (Field field : fields) {
            list.add(field.getName());
        }
        return new StatUserVo(list, rowsOrderBeans);
    }

    @Override
    public StatUserVo statGoods() {
        List<RowsGoodsBean> rowsGoodsBeans = mallGoodsMapper.selectGoodsStatistics();
        Field[] fields = RowsGoodsBean.class.getDeclaredFields();
        ArrayList<String> list = new ArrayList<>();
        for (Field field : fields) {
            list.add(field.getName());
        }
        return new StatUserVo(list, rowsGoodsBeans);
    }

    @Override
    public ConfigMallVo configMall() {
        ConfigMallVo configMallVo = new ConfigMallVo();
        configMallVo.setMarket_mall_address(mallSystemMapper.selectSystemValueByKeyName("address"));
        configMallVo.setMarket_mall_longitude(mallSystemMapper.selectSystemValueByKeyName("longitude"));
        configMallVo.setMarket_mall_qq(mallSystemMapper.selectSystemValueByKeyName("mall_qq"));
        configMallVo.setMarket_mall_name(mallSystemMapper.selectSystemValueByKeyName("mall_name"));
        configMallVo.setMarket_mall_latitude(mallSystemMapper.selectSystemValueByKeyName("latitude"));
        configMallVo.setMarket_mall_phone(mallSystemMapper.selectSystemValueByKeyName("phone"));
        return configMallVo;
    }

    @Override
    public void updateConfigMall(ConfigMallVo configMallVo) {
        //获取key_name
        Field[] keyNames = configMallVo.getClass().getDeclaredFields();
        List<ConfigBo> pushs = new ArrayList<>();
        ConfigBo configMallBo = null;
        for (Field keyName : keyNames) {
            if ("market_mall_address".equals(keyName.getName())) {
                configMallBo = new ConfigBo();
                configMallBo.setName(keyName.getName());
                configMallBo.setValue(configMallVo.getMarket_mall_address());
                pushs.add(configMallBo);
            }
            if ("market_mall_latitude".equals(keyName.getName())) {
                configMallBo = new ConfigBo();
                configMallBo.setName(keyName.getName());
                configMallBo.setValue(configMallVo.getMarket_mall_latitude());
                pushs.add(configMallBo);
            }
            if ("market_mall_longitude".equals(keyName.getName())) {
                configMallBo = new ConfigBo();
                configMallBo.setName(keyName.getName());
                configMallBo.setValue(configMallVo.getMarket_mall_longitude());
                pushs.add(configMallBo);
            }
            if ("market_mall_name".equals(keyName.getName())) {
                configMallBo = new ConfigBo();
                configMallBo.setName(keyName.getName());
                configMallBo.setValue(configMallVo.getMarket_mall_name());
                pushs.add(configMallBo);
            }
            if ("market_mall_phone".equals(keyName.getName())) {
                configMallBo = new ConfigBo();
                configMallBo.setName(keyName.getName());
                configMallBo.setValue(configMallVo.getMarket_mall_phone());
                pushs.add(configMallBo);
            }
            if ("market_mall_qq".equals(keyName.getName())) {
                configMallBo = new ConfigBo();
                configMallBo.setName(keyName.getName());
                configMallBo.setValue(configMallVo.getMarket_mall_qq());
                pushs.add(configMallBo);
            }
        }
        mallSystemMapper.updateByConfigMallVoList(pushs);
    }

    @Override
    public ConfigExpressVo configExpress() {
        ConfigExpressVo configExpressVo = new ConfigExpressVo();
        configExpressVo.setMarket_express_freight_min(mallSystemMapper.selectSystemValueByKeyName("freight_min"));
        configExpressVo.setMarket_express_freight_value(mallSystemMapper.selectSystemValueByKeyName("freight_value"));
        return configExpressVo;
    }

    @Override
    public void updateConfigExpress(ConfigExpressBo configExpressBo) {
        Field[] fields = configExpressBo.getClass().getDeclaredFields();
        ArrayList<ConfigBo> configBos = new ArrayList<>();
        for (Field field : fields) {
            if ("market_express_freight_min".equals(field.getName())) {
                ConfigBo configBo = new ConfigBo();
                configBo.setName(field.getName());
                configBo.setValue(configExpressBo.getMarket_express_freight_min());
                configBos.add(configBo);
            }
            if ("market_express_freight_value".equals(field.getName())) {
                ConfigBo configBo = new ConfigBo();
                configBo.setName(field.getName());
                configBo.setValue(configExpressBo.getMarket_express_freight_value());
                configBos.add(configBo);
            }
        }
        mallSystemMapper.updateByConfigMallVoList(configBos);
    }
}
